﻿/**	@file		thread.h
 *	@date		(2005-11-13 00:08:13)/(2013-04-05 22:35:31)
 *-----------------------------------------------------------------------------
 *	\brief		线程对象.
 *	@version	1.1.27.31
 *	@author		Nick Shallery	(nicknide@gmail.com)
 *	@copyright	YOU HAVE ALL LEFT WITH THIS CODE WHILE YOU KEEP COMMENT IN EVERY COPY.
 *-----------------------------------------------------------------------------
**/


#if			!defined(__LOLIX__LOLI__THREAD__NICK__K_IN_G__)
#define		__LOLIX__LOLI__THREAD__NICK__K_IN_G__


#if			!defined(__LOLIX__LOLI_X_CFG__K_IN_G__)
	#include	"../lolix_cfg.h"
#endif	//	!defined(__LOLIX__LOLI_X_CFG__K_IN_G__)

#if			!defined(__LOLIX__LOLIX_TYPE__K_IN_G__)
	#include	"../lolix_type.h"
#endif	//	!defined(__LOLIX__LOLIX_TYPE__K_IN_G__)

#if			!defined(__LOLIX__TOY__INVOKE_CAST__HPP__K_IN_G__)
	#include	"../toy/invoke_cast.hpp"
#endif	//	!defined(__LOLIX__TOY__INVOKE_CAST__HPP__K_IN_G__)

#if			!defined(__LOLIX__TOY__TIME_TYPES__K_IN_G__)
	#include	"../toy/time_types.h"
#endif	//	!defined(__LOLIX__TOY__TIME_TYPES__K_IN_G__)


namespace lolix{namespace loli{
	class	thread;
	class	thread_factory;
}}

namespace lolix{namespace toy{
	class time_span;
}}


class	LOLIX_NO_VTABLE	lolix::loli::thread
	: public itf
{
public:
	LOLIX_DECLARE_ITF(lolix::loli::thread, lolix::itf, (0x93623933, 0x238f4321, 0x8503338c, 0xbb9e26e7));
	typedef lolix::toy::invoker_process<LOLIX_RETNV, false, lolix::toy::type_list<thread*>, void> FN_INVOKE_PROC;
	STATIC_ASSERT(sizeof(FN_INVOKE_PROC) == 2*sizeof(void*));

	class query;

	enum ENUM_THREAD_START
	{
		THREAD_START_NORMAL		= 0,	//	start normal
		THREAD_START_TRAP		= 1,	//	trap model
		THREAD_START_SUSPEND	= 2,	//	start at SUSPEND

		THREAD_START_VER		= 1,
	};


	enum ENUM_THREAD_STATE
	{
		THREAD_STATE_IDLE		,	//	空闲, 工作完毕后的状态
		THREAD_STATE_WORK		,	//	工作
		//	-----------------------------------
		THREAD_STATE_NUM		,
		THREAD_STATE_VER = 2
	};
	//===========================================================================
	//	start
	//---------------------------------------------------------------------------
	//	@start_param		[i ]	: 启动参数 ENUM_THREAD_START
	//	@q					[i ]	: 调用的对象
	//	@auto_inc_release	[i ]	: 如果 q 对应的对象是 itf 继承下来的， 则可以
	//		标记这个来自动增加和释放引用防止对象生命期短于线程
	//===========================================================================
	LOLIX_INTERFACE(start	, LOLIX_RETNV, (size_type start_param, FN_INVOKE_PROC q, bool auto_inc_release));
	LOLIX_INTERFACE(suspend	, LOLIX_RETNV, (size_type* out_stimes));
	LOLIX_INTERFACE(resume	, LOLIX_RETNV, (size_type* out_stimes));
	LOLIX_INTERFACE(kill	, LOLIX_RETNV, (size_type exit_code));
	LOLIX_INTERFACE(wait	, LOLIX_RETNV, (LOLIX_RETNV* exit_id, const toy::time_span*)const);
	LOLIX_INTERFACE(sleep	, LOLIX_RETNV, (toy::time_span*));
	LOLIX_INTERFACE(state	, LOLIX_RETNV, (ENUM_THREAD_STATE* out_ptr)const);
	LOLIX_INTERFACE(tid		, size_type	,	(void)const);

	template<typename _Ta, typename _Tb>
	LOLIX_RETNV LOLIX_INLINE_CALL start(size_type start_param, _Ta* qi, LOLIX_RETNV (LOLIX_CALL _Tb::*proc)(thread*))
		{
		return this->start(start_param, FN_INVOKE_PROC((_Tb*)qi, proc), type::type_inherit<itf, _Ta>::value);
		}
	template<typename _Ta, typename _Tb>
	LOLIX_RETNV LOLIX_INLINE_CALL start(size_type start_param, _Ta qi, LOLIX_RETNV (LOLIX_CALL _Tb::*proc)(thread*))
		{
		return this->start(start_param, FN_INVOKE_PROC((_Tb*)qi, proc), type::type_inherit<itf, typename _Ta::element_type>::value);
		}
};


class	LOLIX_NO_VTABLE lolix::loli::thread_factory
	: public itf
{
public:
	LOLIX_DECLARE_ITF(lolix::loli::thread_factory, lolix::itf, (0xb9319a7d, 0x26a94b95, 0x94b768c1, 0xd3bfbb8b));
	LOLIX_INTERFACE(create_inst	, LOLIX_RETNV, (thread** out_ptr));
	LOLIX_INTERFACE(local_thread, LOLIX_RETNV, (thread** out_ptr)const);
	LOLIX_INTERFACE(local_id,	LOLIX_RETNV, (lolix::lx_u32* td_id)const);
};



class	LOLIX_NO_VTABLE	lolix::loli::thread::query
	: public itf
{
public:
	typedef	LOLIX_RETNV	value_type;
	LOLIX_DECLARE_ITF(lolix::loli::thread::query, lolix::itf, (0xf124c5e5, 0x28a04730, 0x9380e95e, 0xb3a843d4));
	//	工作函数
	LOLIX_INTERFACE(invoke, LOLIX_RETNV, (void));
};





#endif	//	!defined(__LOLIX__LOLI__THREAD__NICK__K_IN_G__)
